import React, { useCallback, useEffect, useRef, useState, useMemo } from 'react';
import { Button, Form, message, Spin } from 'antd';
import { defaultFormatResult, useRequest } from '@/hooks';
import { debounce } from 'lodash';
import pageTabUtil from '@/utils/pageTabUtil';
import RecordButton from '@/pages/Recruitment/containers/RecordButton';
import { PageContainer } from '@/molecules';
import { TitleControl } from '@/pages/Recruitment/components';
import { ProfileCard } from '@/containers';
import { BottomAction } from '@/components';
import { changeTalkAudioRecordState, getTalkAudioRecordState, getTalkProcedure, onSaveTalkProcedure, resetTalkRecordState, getTalkDetail } from '../../service';
import { useBeforeInterview, useMultiInterviewers } from '../hooks';
import styles from './index.less';
import { RecordQuestion, TalkArrange, TalkEvaluation } from '../containers';
import { hintList } from './enum';

const currentUserCode = JSON.parse(localStorage.getItem('user') ?? null)?.employeeCode;
const isCurrentUser = code => code === currentUserCode;

const formatComment = (source, type) => (source || []).find(commentItem =>
    (isCurrentUser(commentItem.createUserInfo.employeeCode) && commentItem.replayType === type)) || {};

const formatAnswer = (source, type) => (source || []).find(commentItem => commentItem.replayType === type) || {};

const Record = ({ form, location }) => {
    const { arrangeId = '', interviewRefCode = '', employeeCode = '' } = location.query;
    const { getFieldDecorator, validateFieldsAndScroll, getFieldValue, setFieldsValue } = form;
    const [pageLoading, setPageLoading] = useState(false);
    // const [evaluationInfo, setEvaluationInfo] = useState({});
    const [procedureData, setProcedureData] = useState({});
    const scrollWrapRef = useRef();
    const recordButtonRef = useRef();
    const disableAll = useMemo(() => procedureData?.interviewArrangeVO?.interviewStatus === '5', [procedureData]);

    const onChangeRecordState = useCallback(async (recordState = 1) => {
        try {
            await changeTalkAudioRecordState({
                arrangeId,
                recordState
            });
            if (recordState === 1) {
                message.success('已开启录音，同时也可针对自定义问题进行单独录音。');
            }
            if (recordState === 2) {
                const interviewQuestions = form.getFieldValue('interviewQuestions');
                const interviewQuestion = form.getFieldValue('interviewQuestion');
                const newInterviewQuestions = interviewQuestions.map(item => {
                    if (!item.answer || !item.answer.answerTimes || !item.answer.answerTimes.length) {
                        return item;
                    }
                    return {
                        ...item,
                        isRecord: false,
                        answer: {
                            ...item.answer,
                            answerTimes: item.answer.answerTimes.map(time => {
                                if (time.endTime) return time;
                                return {
                                    ...time,
                                    endTime: new Date().getTime()
                                };
                            })
                        }
                    };
                });
                form.setFieldsValue({
                    // 用于强行让form能够再次检测interviewQuestion
                    interviewQuestion: interviewQuestion
                        ? interviewQuestion.map(item => ({
                            submitCheck: !item.submitCheck
                        }))
                        : [],
                    interviewQuestions: newInterviewQuestions
                });
            }
        } catch (e) {
            console.log(e);
        }
    }, []);
    const getRecordState = useCallback(async recordType => {
        try {
            const { data, code } = await getTalkAudioRecordState({
                arrangeId,
                recordType
            });
            return code === 10000 ? data : 3;
        } catch (e) {
            console.log(e);
            return 3;
        }
    }, []);

    // 轮询
    const { run: runPolling, cancel: cancelPolling } = useRequest(() => getTalkProcedure(arrangeId), {
        ...defaultFormatResult,
        manual: true,
        pollingInterval: 5000,
        onSuccess(result) {
            const { otherQuestions: data = [] } = result || {};
            if (!data.length) {
                return;
            }
            let render = false;
            let nextFormList = (getFieldValue('interviewQuestions') || []).slice();
            const selfFormList = nextFormList.filter(item => item.isEqual);
            data.forEach((item, index) => {
                const { id: newId, createUserInfo = {}, title: newQuestion } = item || {};
                const newAnswer = formatAnswer(item.comment, '1');
                const { employeeName } = createUserInfo;
                const oldIndex = nextFormList.findIndex(old => old.id === newId);
                // 新增
                const selfFormLen = selfFormList.length;
                if (oldIndex === -1) {
                    render = true;
                    const len = selfFormLen + index + 1;
                    message.info(`${employeeName} 新增了自定义问题 ${len}`);
                } else {
                    // 更新
                    const old = nextFormList[oldIndex] || {};
                    const { title: oldQuestion, answer: oldAnswer } = old;
                    const newAnswerContent = newAnswer?.content;
                    const oldAnswerContent = oldAnswer?.content;
                    if (newQuestion !== oldQuestion) {
                        render = true;
                        message.info(`${employeeName} 更新了自定义问题 ${oldIndex + 1}`);
                    }
                    if (oldAnswerContent !== newAnswerContent) {
                        render = true;
                        message.info(`${employeeName} 更新了自定义问题 ${oldIndex + 1} 的候选人答复`);
                    }
                    // eslint-disable-next-line no-param-reassign
                    data[index] = {
                        ...old,
                        ...item
                    }
                }
            });
            const removed = [];
            // 移除删除的
            nextFormList = nextFormList.filter((old, index) => {
                const parse = old.isEqual || data.findIndex(current => current.id === old.id) !== -1;
                if (!parse) {
                    render = true;
                    removed.push({
                        number: index + 1,
                        employeeName: old?.createUserInfo?.employeeName
                    });
                }
                return parse;
            });
            removed.forEach(item => {
                message.info(`${item.employeeName} 删除了自定义问题 ${item.number}`);
            });
            if (render) {
                const otherQuestions = data.map(item => {
                    const answer = formatAnswer(item.comment, '1');
                    const comment = formatComment(item.comment, '2');
                    return {
                        ...item,
                        comment,
                        answer
                    };
                });
                // console.log(otherQuestions, '===========')
                setFieldsValue({
                    interviewQuestions: [...selfFormList, ...otherQuestions]
                });
            }
        }
    });

    const getInfo = async () => {
        try {
            setPageLoading(true);
            const { data = {}, code } = await getTalkDetail(arrangeId);
            const { interviewArrangeVO = {} } = data;
            console.log('面谈记录数据', data);
            // 取完数据后启动轮询
            runPolling();
            if (code === 10000) {
                const { questions = {} } = interviewArrangeVO;
                let {
                    myQuestions = [],
                    otherQuestions = []
                } = questions;
                myQuestions = myQuestions.map(item => {
                    const answer = formatComment(item.comment, '1');
                    const comment = formatComment(item.comment, '2');
                    console.log(answer);
                    return {
                        ...item,
                        comment,
                        answer: { ...answer, answerTimes: item?.interviewAnswerTimeDTOList || [] },
                        isEqual: true
                    };
                });
                otherQuestions = otherQuestions.map(item => {
                    const answer = formatAnswer(item.comment, '1');
                    const comment = formatComment(item.comments, '2');
                    return {
                        ...item,
                        comment,
                        answer
                    };
                });
                setProcedureData(data);
                setFieldsValue({
                    interviewQuestions: [...myQuestions, ...otherQuestions]
                });
            }
            setPageLoading(false);
        } catch (e) {
            console.log(e);
            setPageLoading(false);
        }
    };
    const onInterviewSubmit = debounce(async () => {
        try {
            validateFieldsAndScroll(async (err, values) => {
                console.log(values);
                if (!err) {
                    const { reason, hasAgree } = values;
                    setPageLoading(true);
                    const params = {
                        dimissionCode: interviewRefCode,
                        arrangeId,
                        reason,
                        hasAgree: !!hasAgree,
                        questionResultDTOList: values.interviewQuestions.map(item => ({
                                answerTimes: item?.answer?.answerTimes ?? [],
                                id: item.id
                            })),
                        ...(recordButtonRef.current ? await recordButtonRef.current.getRecordInfo() : {})
                    };
                    const { code, msg } = await onSaveTalkProcedure(params);
                    if (code === 10000) {
                        message.success('提交成功！');
                        pageTabUtil.goBack();
                    } else {
                        message.error(msg);
                    }
                    setPageLoading(false);
                }
            });
        } catch (e) {
            console.log(e);
            setPageLoading(false);
        }
    }, 400);

    useEffect(() => {
        message.config({
            maxCount: 100
        });
        getInfo();
        // 临时解决：录音启动后退出页面无法继续录音的操作
        resetTalkRecordState(arrangeId);
        return () => {
            cancelPolling();
            // 在request.js中有对这个做限制，把它还原
            message.config({
                maxCount: 1
            });
        };
    }, []);

    // 面试前校验
    useBeforeInterview({ arrangeId });

    // 多面试官相关处理逻辑
    const { onBeforeStart, recordStatusMsg, setIntervalActive } = useMultiInterviewers({ arrangeId });

    const extraRecordButtonProps = {
        onBeforeStart,
        recordStatusMsg,
        setIntervalActive
    };

    const recordUrl = procedureData?.interviewArrangeVO?.recordUrl;
    const renderRecorder = () => {
        if (!recordUrl) {
            return (
                <RecordButton
                    guideMsg={<div>面谈开始后请<span style={{ fontWeight: 'bold' }}>及时进行录音</span></div>}
                    isGuide
                    cRef={recordButtonRef}
                    scrollWrapRef={scrollWrapRef}
                    getRecordState={() => getRecordState(0)}
                    onChangeRecordState={onChangeRecordState}
                    hintList={hintList}
                    guideKey="leaving_talk_record"
                    {...extraRecordButtonProps}
                />
            );
        }
        return (
            <audio src={recordUrl} controls="controls" style={{ height: 30, width: 240 }}>
                <track kind="captions" />
            </audio>
        );
    };
    return (
        <div ref={scrollWrapRef}>
            <PageContainer>
                <Spin spinning={pageLoading}>
                    <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center' }}>
                        <ProfileCard employeeCode={employeeCode}/>
                        { renderRecorder() }
                    </div>
                    <TitleControl title="面试安排">
                        <TalkArrange
                            data={procedureData?.interviewArrangeVO}
                            dimissionInfo={procedureData?.dimissionOrderVO}
                        />
                    </TitleControl>
                    <TitleControl title="面谈问题">
                        <div className={styles.questionTip}>完成编辑后，答复将同步展示给其他面谈官</div>
                        {getFieldDecorator('interviewQuestions', {
                            initialValue: []
                        })(
                            <RecordQuestion
                                form={form}
                                getRecordState={() => getRecordState(1)}
                                arrangeId={arrangeId}
                                disableButton={!!recordUrl}
                                scrollWrapRef={scrollWrapRef}
                                disableAll={disableAll}
                            />
                        )}
                    </TitleControl>
                    <TitleControl title="面谈建议" bottomBorder={false} showButton={false}>
                        <div className={styles.questionTip}>将同步给审批人作为参考，非最终结论</div>
                        <TalkEvaluation
                            form={form}
                            style={{ width: 460 }}
                            loading={pageLoading}
                            interviewerEmployeeInfo={procedureData?.interviewArrangeVO?.interviewerEmployeeInfo || []}
                        />
                    </TitleControl>
                    {
                        !disableAll && <BottomAction>
                            <Button onClick={() => pageTabUtil.goBack()} style={{ marginRight: 8 }}>
                                取消
                            </Button>
                            <Button type="primary" onClick={onInterviewSubmit} loading={pageLoading}>
                                提交
                            </Button>
                        </BottomAction>
                    }
                </Spin>
            </PageContainer>
        </div>
    );
};

export default Form.create()(Record);
